/*******************************************************************************
 * @(#)ResInterceptor.java 2019年08月29日 17:11
 * Copyright 2019 upbos.com. All rights reserved.
 *******************************************************************************/
package com.upbos.sso.plugin;

import cn.hutool.http.HttpStatus;
import com.upbos.core.ret.RetCode;
import com.upbos.core.ret.RetData;
import com.upbos.sso.entity.SsoContext;
import com.upbos.sso.entity.Token;
import com.upbos.sso.Constants;
import com.upbos.sso.filter.ChainRet;
import com.upbos.sso.util.ServletUtils;
import org.springframework.util.AntPathMatcher;
import org.springframework.util.PathMatcher;

import javax.servlet.http.HttpServletRequest;
import javax.servlet.http.HttpServletResponse;
import java.util.ArrayList;
import java.util.Arrays;
import java.util.List;

/**
 * <b>Application name：</b> ResInterceptor.java <br>
 * <b>Application describing： 校验Token是否有效</b> <br>
 * <b>Copyright：</b> Copyright &copy; 2019 upbos.com 版权所有。<br>
 * <b>Company：</b> upbos.com <br>
 * <b>@Date：</b> 2019年08月29日 17:11 <br>
 * <b>@author：</b> <a href="mailto:Jason@miyzh.com"> Jason </a> <br>
 * <b>@version：</b>V5.0.0 <br>
 */
public class ResInterceptor implements Interceptor {

    /**
     * 自定义忽略校验的资源
     */
    private List<String> excludeUrls = new ArrayList<>(Arrays.asList("/**/common/**"));


    public void setExcludeUrls(List<String> excludeUrls) {
        this.excludeUrls.addAll(excludeUrls);
    }

    @Override
    public ChainRet preHandle(HttpServletRequest request, HttpServletResponse response, SsoContext ssoContext) {
        PathMatcher matcher = new AntPathMatcher();
        String requestUri = request.getRequestURI();

        // 放行登录页面列表
        if (matchIndex(request, ssoContext.getLoginUrls(), matcher) > -1) {
            return ChainRet.SKIP;
        }

        // 放行例外页面
        if (matchIndex(request, excludeUrls, matcher) > -1) {
            return ChainRet.SKIP;
        }

        Token token = ssoContext.getSsoManager().getToken(request);
        if (token == null) {
            return ChainRet.BREAK;
        }
        List<String> resList = ssoContext.getSsoManager().getAttr(token.getId(), Constants.SESSION_CACHE_RES_KEY_NAME);
        if (resList != null) {
            for (String res : resList) {
                if (matcher.match(res, requestUri)) {
                    return ChainRet.NEXT;
                }
            }
        }

        RetData retData = new RetData(RetCode.RESOURCE_UNAUTHORIZED);
        response.setStatus(HttpStatus.HTTP_INTERNAL_ERROR);
        ServletUtils.write(response, retData);
        return ChainRet.BREAK;
    }

    /**
     * 拦截器执行优先级
     *
     * @return
     */
    @Override
    public int getPriority() {
        return 2;
    }

    @Override
    public String getName() {
        return Constants.INTERCEPTOR_RES;
    }
}
